{
 "cells": [
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "## 常规的线程无法控制线程锁的切换\n",
    "\n",
    "import threading\n",
    "\n",
    "class XiaoAi(threading.Thread):\n",
    "    def __init__(self, lock):\n",
    "        super().__init__(name=\"小爱\")\n",
    "        self.lock.lock\n",
    "        \n",
    "    def run(self):\n",
    "        print(\"{}: 在 \".format(self.name))\n",
    "    \n",
    "class TianMao(threading.Thread):\n",
    "    def __init__(self, lock):\n",
    "        super().__init__(name=\"天猫\")\n",
    "        self.lock.lock\n",
    "        \n",
    "    def run(self):\n",
    "        self.lock.acquire()\n",
    "        print(\"{}: 小爱同学 \".format(self.name))\n",
    "        self.lock.release()\n",
    "        \n",
    "if __name__ == \"__main__\":\n",
    "    lock = threading.Lock()\n",
    "    \n",
    "    xiaoai = XiaoAi(lock)\n",
    "    tianmao = TianMao(lock)\n",
    "    \n",
    "    xiaoai.start()\n",
    "    tianmao.start()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "天猫精灵 : 小爱同学 \n",
      "小爱 : 在 \n",
      "天猫精灵 : 我们来对古诗吧 \n",
      "小爱 : 好啊 \n",
      "天猫精灵 : 我住长江头 \n",
      "小爱 : 君住长江尾 \n",
      "天猫精灵 : 日日思君不见君 \n",
      "小爱 : 共饮长江水 \n",
      "天猫精灵 : 此水几时休 \n",
      "小爱 : 此恨何时已 \n",
      "天猫精灵 : 只愿君心似我心 \n",
      "小爱 : 定不负相思意 \n"
     ]
    }
   ],
   "source": [
    "## 条件变量，用于复杂的线程间同步\n",
    "## 通过condition 完成协同读诗\n",
    "## 常用方法：\n",
    "## wait：允许等待某个条件变量的通知\n",
    "## notify：通知我们调用wait方法的线程启动\n",
    "\n",
    "import threading\n",
    "\n",
    "class XiaoAi(threading.Thread):\n",
    "    def __init__(self, cond):\n",
    "        super().__init__(name=\"小爱\")\n",
    "        self.cond = cond\n",
    "\n",
    "    def run(self):\n",
    "        with self.cond:\n",
    "            self.cond.wait()\n",
    "            print(\"{} : 在 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "\n",
    "            self.cond.wait()\n",
    "            print(\"{} : 好啊 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "\n",
    "            self.cond.wait()\n",
    "            print(\"{} : 君住长江尾 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "\n",
    "            self.cond.wait()\n",
    "            print(\"{} : 共饮长江水 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "\n",
    "            self.cond.wait()\n",
    "            print(\"{} : 此恨何时已 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "\n",
    "            self.cond.wait()\n",
    "            print(\"{} : 定不负相思意 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "\n",
    "class TianMao(threading.Thread):\n",
    "    def __init__(self, cond):\n",
    "        super().__init__(name=\"天猫精灵\")\n",
    "        self.cond = cond\n",
    "\n",
    "    def run(self):\n",
    "        with self.cond:\n",
    "            print(\"{} : 小爱同学 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "            self.cond.wait()\n",
    "\n",
    "            print(\"{} : 我们来对古诗吧 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "            self.cond.wait()\n",
    "\n",
    "            print(\"{} : 我住长江头 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "            self.cond.wait()\n",
    "\n",
    "            print(\"{} : 日日思君不见君 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "            self.cond.wait()\n",
    "\n",
    "            print(\"{} : 此水几时休 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "            self.cond.wait()\n",
    "\n",
    "            print(\"{} : 只愿君心似我心 \".format(self.name))\n",
    "            self.cond.notify()\n",
    "            self.cond.wait()\n",
    "\n",
    "\n",
    "\n",
    "if __name__ == \"__main__\":\n",
    "    from concurrent import futures\n",
    "    cond = threading.Condition()\n",
    "    xiaoai = XiaoAi(cond)\n",
    "    tianmao = TianMao(cond)\n",
    "\n",
    "    ## 启动顺序很重要\n",
    "    ## 在调用with cond之后才能调用wait或者notify方法\n",
    "    ## condition有两层锁， 一把底层锁会在线程调用了wait方法的时候释放， \n",
    "    ## 上面的锁会在每次调用wait的时候分配一把并放入到cond的等待队列中，等到notify方法的唤醒\n",
    "    \n",
    "    xiaoai.start()\n",
    "    tianmao.start()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.7.4"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
